﻿namespace EFS.RC.Wallboard.Controls
{
	/// Class MainWindow
	public partial class MainWindow : EFS.RC.ClientPlatform.UI.MainWindow
	{
		#region Delegates

		/// LoadEndPointsDelegate
		private delegate void LoadEndPointDelegate(EFS.RC.CC.Messages.Application.CustomerEndPoint customerEndPointMsg);

		/// UpdateAgentsStatusList
		private delegate void UpdateAgentsStatusListDelegate(EFS.RC.CC.Messages.Agents.StatusList statusListMsg);

		/// LoadEndPointsDelegate
		private delegate void UpdateHuntQueueStatusListDelegate(EFS.RC.CC.Messages.HuntQueue.StatusList statusListMsg);

		#endregion

		#region Locals

		/// all customer endpoints tab items or null if filtered out
		private System.Collections.Generic.Dictionary<System.String, EFS.RC.Wallboard.Controls.Endpoints.Customer.Main> customerEndPointMainControls =
			new System.Collections.Generic.Dictionary<System.String, EFS.RC.Wallboard.Controls.Endpoints.Customer.Main>();

		// all end points
		private System.Collections.Generic.SortedDictionary<System.String, EFS.RC.CC.Messages.Application.CustomerEndPoint> customerEndPoints =
			new System.Collections.Generic.SortedDictionary<System.String, EFS.RC.CC.Messages.Application.CustomerEndPoint>();

		#endregion

		#region Constructors

		/// Implicit
		public MainWindow()
		{
			InitializeComponent();

			// add key down event
			AddHandler(System.Windows.Input.Keyboard.KeyDownEvent, (System.Windows.Input.KeyEventHandler)HandleKeyDownEvent);

			// init ui
			InitUI();
		}

		#endregion

		#region UI

		/// InitUI
		private void InitUI()
		{
			// ignore in design tool
			if (!System.ComponentModel.DesignerProperties.GetIsInDesignMode(this))
			{
				ClearUIPhones();
			}
		}

		/// <summary>
		/// Get index in phone list 
		/// </summary>
		/// <param name="s"></param>
		/// <returns></returns>
		private static System.Int32 IndexOf(string s)
		{
			return EFS.RC.Wallboard.Common.Config.Settings.FilterPhones.IndexOf(s);
		}

		/// AddCustomerEndPoint
		private void AddCustomerEndPoint(EFS.RC.CC.Messages.Application.CustomerEndPoint customerEndPoint)
		{
			// keep;
			customerEndPoints[customerEndPoint.PhoneUri] = customerEndPoint;

			// create array
			System.Collections.Generic.List<System.String> phones = new System.Collections.Generic.List<System.String>();
			foreach (System.String phone in customerEndPoints.Keys)
			{
				// check filtered
				if (EFS.RC.Wallboard.Common.Config.Settings.FilterPhones.IndexOf(phone) < 0)
				{
					continue;
				}

				// add to list
				phones.Add(phone);
			}

			// load
			phones.Sort((a, b) => IndexOf(a).CompareTo(IndexOf(b)));
			LoadPhones(phones.ToArray());
		}

		/// ClearUIPhones
		private void ClearUIPhones()
		{
			// remove all others
			customerEndPointMainControls.Clear();
			gridPhones.RowDefinitions.Clear();

			// cicle all and reset
			gridPhones.Children.Clear();
		}

		/// UpdateAgentsStatusList
		private void UpdateAgentsStatusList(EFS.RC.CC.Messages.Agents.StatusList statusListMsg)
		{
			foreach (EFS.RC.Wallboard.Controls.Endpoints.Customer.Main mainCtrl in customerEndPointMainControls.Values)
			{
				// check if tab available
				if (null != mainCtrl)
				{
					mainCtrl.LoadData(statusListMsg);
				} 
			}
		}

		/// UpdateHuntQueueStatusList
		private void UpdateHuntQueueStatusList(EFS.RC.CC.Messages.HuntQueue.StatusList statusListMsg)
		{
			// test & update
			if (EFS.Common.UI.Shared.WindowHelper.IsDisposed(this))
			{
				return;
			}

			// cicle all
			foreach (EFS.RC.CC.Messages.HuntQueue.Status status in statusListMsg.Items)
			{
				// check of end point here
				if (!customerEndPointMainControls.ContainsKey(status.PhoneUri))
				{
					continue;
				}

				// get content control
				EFS.RC.Wallboard.Controls.Endpoints.Customer.Main ctrlMain = customerEndPointMainControls[status.PhoneUri];
				 
				// first row
				ctrlMain.controlFirstGroup.CW = status.WaitCount;
				ctrlMain.controlFirstGroup.LW = new System.TimeSpan(status.LongestWatingTime);

				// second row
				ctrlMain.controlSecondGroup.TotalCalls = status.TotalCalls;
				ctrlMain.controlSecondGroup.AverageAnswer = new System.TimeSpan(status.AverageWatingTime);
				ctrlMain.controlSecondGroup.Abandon = status.TotalDroppedCalls;
			}
		}

		#endregion

		#region Utilities
		/// Load phones
		private void LoadPhones(System.String[] phones)
		{
			// check
			EFS.Common.Verify.Reference(phones, "phones");

			// remove all others
			ClearUIPhones();

			// add
			for (System.Int32 i = 0; i < phones.Length; ++i)
			{
				// add row definition
				System.Windows.Controls.RowDefinition rowDefinition = new System.Windows.Controls.RowDefinition();
				gridPhones.RowDefinitions.Add(rowDefinition);

				// create control
				EFS.RC.Wallboard.Controls.Endpoints.Customer.Main controlMain = new EFS.RC.Wallboard.Controls.Endpoints.Customer.Main();
				controlMain.CustomerEndPoint = customerEndPoints[phones[i]];
				controlMain.VerticalAlignment = System.Windows.VerticalAlignment.Stretch;
				controlMain.VerticalContentAlignment = System.Windows.VerticalAlignment.Stretch;
				controlMain.HorizontalAlignment = System.Windows.HorizontalAlignment.Stretch;
				controlMain.HorizontalContentAlignment = System.Windows.HorizontalAlignment.Stretch;
				controlMain.Margin = new System.Windows.Thickness(0, 0, 0, 0);

				// add to hash
				customerEndPointMainControls[phones[i]] = controlMain;

				// add to grid
				gridPhones.Children.Add(controlMain);
				System.Windows.Controls.Grid.SetRow(controlMain, i);
				System.Windows.Controls.Grid.SetColumn(controlMain, 0);
			}
		}

		/// <summary>
		/// apply filter
		/// </summary>
		private void ApplyPhonesFilter()
		{
			// check eny new and add
			System.String[] phones = EFS.RC.Wallboard.Common.Config.Settings.FilterPhones.Split(new System.Char[] { ';' }, System.StringSplitOptions.RemoveEmptyEntries);

			// load phones
			LoadPhones(phones);
		}
		#endregion

		#region Window events
		/// HandleKeyDownEvent
		private void HandleKeyDownEvent(System.Object sender, System.Windows.Input.KeyEventArgs e)
		{
			// CTRL + something
			if ((System.Windows.Input.Keyboard.Modifiers & System.Windows.Input.ModifierKeys.Control) == System.Windows.Input.ModifierKeys.Control)
			{
				// Q
				if (e.Key == System.Windows.Input.Key.Q)
				{
					ClosePlatform();
				}
			}
		}

		/// Loaded
		private void mainWindow_Loaded(object sender, System.Windows.RoutedEventArgs e)
		{
			// load feeds
			controlRssList.Start();
		}

		/// Closed
		private void mainWindow_Closed(object sender, System.EventArgs e)
		{
			// stop swap
			controlRssList.Stop();
		}
		#endregion

		#region MenuEvents

		/// File
		private void menuItemFile_Click(object sender, System.Windows.RoutedEventArgs e)
		{
			System.Windows.Controls.MenuItem mi = e.Source as System.Windows.Controls.MenuItem;

			switch (mi.Name)
			{
				case "menuItemFileExit":
					{
						ClosePlatform();
						break;
					}
				default:
					{
						break;
					}
			}
		}

		/// Tools
		private void menuItemTools_Click(object sender, System.Windows.RoutedEventArgs e)
		{
			System.Windows.Controls.MenuItem mi = e.Source as System.Windows.Controls.MenuItem;

			switch (mi.Name)
			{
				case "menuItemToolsFilterPhones":
					{
						EFS.RC.Wallboard.Controls.FilterPhones filter = new FilterPhones(customerEndPoints.Keys);
						filter.Owner = this;
						filter.ShowDialog();
						ApplyPhonesFilter();
						break;
					}
				default:
					{
						break;
					}
			}
		}

		#endregion

		#region Messages

		// terminated
		protected override void SessionTerminatedCleanup()
		{
			// clear tabs
			//tabControlMain.Items.Clear();
		}

		/// Process Message entry point
		protected override void ProcessUCMAMessage(EFS.RC.CC.Messages.Message message)
		{
			try
			{
				// test message
				if (null != message)
				{
					// CustomerEndPointList
					if (message is EFS.RC.CC.Messages.Application.CustomerEndPoint)
					{
						ProcessUCMAMessage_CustomerEndPoint(message as EFS.RC.CC.Messages.Application.CustomerEndPoint);
					}
					// Agents StatusList
					else if (message is EFS.RC.CC.Messages.Agents.StatusList)
					{
						ProcessUCMAMessage_AgentsStatusList(message as EFS.RC.CC.Messages.Agents.StatusList);
					}
					// HuntQueue StatusList
					else if (message is EFS.RC.CC.Messages.HuntQueue.StatusList)
					{
						ProcessUCMAMessage_HuntQueueStatusList(message as EFS.RC.CC.Messages.HuntQueue.StatusList);
					}
				}
			}
			catch (System.Exception ex)
			{
				EFS.EventLog.Log.LogException(ex, null);
			}
		}

		/// CustomerEndPointList
		private void ProcessUCMAMessage_CustomerEndPoint(EFS.RC.CC.Messages.Application.CustomerEndPoint customerEndPointMsg)
		{
			this.Dispatcher.Invoke(
				new LoadEndPointDelegate(AddCustomerEndPoint),
				new System.Object[] { customerEndPointMsg });

#if DEBUG
#warning JUST FOR TEST
			EFS.RC.CC.Messages.Application.CustomerEndPoint customerEndPointMsg2 = new CC.Messages.Application.CustomerEndPoint();
			customerEndPointMsg2.PhoneUri = "TEL:+0002";
			customerEndPointMsg2.RequiredSkillId = 1;
			this.Dispatcher.Invoke(
				new LoadEndPointDelegate(AddCustomerEndPoint),
				new System.Object[] { customerEndPointMsg2 });
#endif
		}

		/// StatusList
		private void ProcessUCMAMessage_AgentsStatusList(EFS.RC.CC.Messages.Agents.StatusList statusListMsg)
		{
			this.Dispatcher.Invoke(
				new UpdateAgentsStatusListDelegate(UpdateAgentsStatusList),
				new System.Object[] { statusListMsg });
		}

		/// StatusList
		private void ProcessUCMAMessage_HuntQueueStatusList(EFS.RC.CC.Messages.HuntQueue.StatusList statusListMsg)
		{
			this.Dispatcher.Invoke(
				new UpdateHuntQueueStatusListDelegate(UpdateHuntQueueStatusList),
				new System.Object[] { statusListMsg });
		}
		#endregion
	}

}